﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading;
using System.Threading.Tasks;

namespace CaseManagerLibrary.Log
{
    public class TextLog : ILog
    {
        private Queue<string> logBuffer = new Queue<string>();
        private Queue<string> errorBuffer = new Queue<string>();

        private Thread writeFileThread;

        private const string blank = "                         ";

        public bool Logging { get; set; }

        public string LogPath { get; set; }
        public bool BringToFront { get; set; }
        public int Left { get; set; }

        public int Top { get; set; }
        public bool Writing { get; private set; }


        private string normalLogPath = "";
        private string errorLogPath = "";

        public TextLog(string logPath)
        {
            Left = 0;
            Top = 0;
            LogPath = logPath;
            normalLogPath = System.IO.Path.Combine(logPath, "Normal");
            errorLogPath = System.IO.Path.Combine(logPath, "Error");

            if (!System.IO.Directory.Exists(normalLogPath))
            {
                System.IO.Directory.CreateDirectory(normalLogPath);
            }

            if (!System.IO.Directory.Exists(errorLogPath))
            {
                System.IO.Directory.CreateDirectory(errorLogPath);
            }
            Writing = false;
            Logging = true;

            writeFileThread = new Thread(new ThreadStart(WriteFile));
            writeFileThread.Start();
        }

        public void Close()
        {
            Logging = false;
        }

        private void WriteFile()
        {
            string logFile;
            string errorFile;

            while (Logging)
            {
                if (logBuffer.Count > 0)
                {
                    logFile = System.IO.Path.Combine(normalLogPath, DateTime.Now.ToString("yyyy-MM-dd") + ".log");

                    var swlog = System.IO.File.AppendText(logFile);

                    while (logBuffer.Count > 0)
                    {
                        Writing = true;
                        swlog.WriteLine(logBuffer.Dequeue());
                    }

                    swlog.Close();
                }

                if (errorBuffer.Count > 0)
                {
                    errorFile = System.IO.Path.Combine(errorLogPath, DateTime.Now.ToString("yyyy-MM-dd") + ".err");

                    var swerror = System.IO.File.AppendText(errorFile);

                    while (errorBuffer.Count > 0)
                    {
                        Writing = true;
                        swerror.WriteLine(errorBuffer.Dequeue());
                    }

                    swerror.Close();
                }

                Writing = false;

                Thread.Sleep(1000);
            }
        }

        public void Error(string text)
        {
            try
            {
                logBuffer.Enqueue("");
                logBuffer.Enqueue(DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss.fff"));
                logBuffer.Enqueue("  ERROR:" + text);

                errorBuffer.Enqueue("");
                errorBuffer.Enqueue(DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss.fff"));
                errorBuffer.Enqueue("  ERROR:" + text);
            }
            catch (Exception ex)
            { }
        }

        public void Info(string text)
        {
            try
            {
                logBuffer.Enqueue("");
                logBuffer.Enqueue(DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss.fff"));
                logBuffer.Enqueue("  INFO:" + text);
            }
            catch (Exception ex)
            { }
        }

        public void Log(string text)
        {
            try
            {
                logBuffer.Enqueue("");
                logBuffer.Enqueue(DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss.fff"));
                logBuffer.Enqueue("  LOG:" + text);
            }
            catch (Exception ex)
            { }
        }

        public void MC()
        {
            try
            {
                logBuffer.Enqueue("MC>");
            }
            catch (Exception ex)
            { }
        }

        public void NewLine()
        {
            try
            {
                logBuffer.Enqueue("");
            }
            catch (Exception ex)
            { }
        }

        public void Text(string text)
        {
            try
            {
                logBuffer.Enqueue("");
                logBuffer.Enqueue(blank + text);
            }
            catch (Exception ex)
            { }
        }
    }
}
